package com.manager.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.easyCode.feature.mybaits.CustomPage;
import com.manager.entity.dao.Manager;
import com.manager.entity.dao.User;
import com.manager.entity.dto.UserDto;
import com.manager.entity.vo.UserVo;
import com.manager.exception.ManagerException;
import com.manager.mapper.UserMapper;
import com.manager.service.ISubCampusService;
import com.manager.service.IUserService;
import com.security.client.AuthClient;
import io.seata.spring.annotation.GlobalTransactional;
import lombok.RequiredArgsConstructor;
import org.apache.commons.lang3.ObjectUtils;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import java.util.Objects;

import static com.manager.constants.ManagerServiceConstants.*;
import static com.manager.entity.factory.UserFactory.USER_CONVERTER;

@Service
@RequiredArgsConstructor
public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements IUserService {
    private final ISubCampusService iSubCampusService;
    private final PasswordEncoder passwordEncoder;
    private final AuthClient authClient;

    @GlobalTransactional
    @Override
    public Integer saveUser(UserVo userVo) {
        iSubCampusService.checkExist(userVo.getCId());
        User user = USER_CONVERTER.toUser(userVo);
        User.nameRepeatCheck(user,this);
        user.setPwd(passwordEncoder.encode(user.getPwd()));
        save(user);
        authClient.registerUser(user.getName(), USER_SERVICE_NAME, COMMON_USER_ROLE_NAME);
        return user.getId();
    }

    @Override
    public UserDto getUserById(Integer id) {
        User user = getById(id);
        if(user==null){
            return null;
        }
        Manager.mustHasVisitSubCampusAuthority(user.getCId());
        return USER_CONVERTER.toUserDto(user);
    }


    @Override
    public List<UserDto> listUser(String queryExample, CustomPage customPage) {
        List<User> userList = null;
        if(Manager.isSuperManager()) {
            userList=CustomPage.getResult(customPage, new User(), this,
                    ObjectUtils.isEmpty(queryExample) ?
                            null : new QueryWrapper<User>().like("name", queryExample));
        }else{
            QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
            if(!ObjectUtils.isEmpty(queryExample)){
                userQueryWrapper.like("name",queryExample);
            }
            List<Integer> managerSubIdList = Manager.getManagerSubIdList();
            if(!ObjectUtils.isEmpty(managerSubIdList)){
                userQueryWrapper.in("c_id",managerSubIdList);
            }
            userList=CustomPage.getResult(customPage, new User(), this, userQueryWrapper);
        }
        return USER_CONVERTER.toListUserDto(userList);
    }

    @GlobalTransactional
    @Override
    public void delUserById(Integer id) {
        User user = getById(id);
        if(user==null){
            return;
        }
        Manager.mustHasVisitSubCampusAuthority(user.getCId());
        authClient.deleteUser(user.getName(),USER_SERVICE_NAME);
        removeById(id);
    }

    @Override
    public Boolean changeUserSubCampus(Integer campusId,Integer userId) {
        iSubCampusService.checkExist(campusId);
        User user = getById(userId);
        if(user==null){
            throw new ManagerException("用户不存在");
        }
        Manager.mustHasVisitSubCampusAuthority(user.getCId());
        return updateById(User.builder().id(userId).cId(campusId).build());
    }

    @Override
    public boolean enableOrDisableUser(Integer userId, Integer enable) {
        User user = getById(userId);
        if(user==null){
            return true;
        }
        Manager.mustHasVisitSubCampusAuthority(user.getCId());
        return updateById(User.builder().id(userId).enable(enable).build());
    }
}
